﻿using BCCommon;
using BCData.TMS.Contraband.ContrabandCategory;
using BCData.TMS.Contraband.ContrabandConfig;
using BCDto.Sim.Admin.Admin;
using BCDto.TMS.Contraband.ContrabandCategory;
using BCEntity.Common.EntityNameConst;
using BCEntity.TMS.Contraband.ContrabandCategory;
using BCService.Utils;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace BCService.TMS.Contraband.ContrabandCategory
{
    public class ContrabandCategoryService : IContrabandCategoryService
    {
        #region var
        private readonly IContrabandCategoryData contrabandCategoryData;
        private readonly IContrabandConfigData contrabandConfigData;
        private readonly IRedisService redisService;
        private readonly string key = string.Format("{0}", EntityNameConst.ContrabandCategoryEntity);


        #endregion

        #region 构造函数
        public ContrabandCategoryService(IContrabandCategoryData contrabandCategoryData,
            IContrabandConfigData contrabandConfigData,
            IRedisService redisService)
        {
            this.contrabandCategoryData = contrabandCategoryData;
            this.contrabandConfigData = contrabandConfigData;
            this.redisService = redisService;
        }
        #endregion

        #region Add
        /// <summary>
        /// 添加新违禁品分类纪录
        /// </summary>
        /// <param name="admin">管理员信息</param>
        /// <param name="requestDto">违禁品分类添加信息</param>
        /// <returns></returns>
        public ContrabandCategoryDto Add(ContrabandCategoryRequestDto requestDto, AdminDto admin)
        {
            if (admin.CompanyId != 1)
            {
                throw new ArgumentException("您不是总公司员工，暂无权限添加");
            }
            if (requestDto.ContrabandCategory.Trim().Length > 30)
            {
                throw new ArgumentException("违禁品分类不能多于30字");
            }
            var result = this.contrabandCategoryData.GetEntityByContrabandCategory(requestDto.ContrabandCategory.Trim()).Result;
            if (result != null)
            {
                throw new ArgumentException("此分类已存在，不需重复添加");
            }
            result = this.contrabandCategoryData.InsertAsync(new ContrabandCategoryEntity()
            {
                ContrabandCategory = requestDto.ContrabandCategory.Trim(),
                CreateAdminId = admin.AdminId,
                CreateAdminName = admin.FullName,
                CreateTime = DateTime.Now,
                UpdateTime = DateTime.Now,
                EditAdminId = admin.AdminId,
                EditAdminName = admin.FullName
            }).GetAwaiter().GetResult();
            this.redisService.DeleteMultipleKey(key, false);
            return result.As<ContrabandCategoryDto>();
        }
        #endregion

        #region update
        /// <summary>
        /// 修改违禁品分类记录
        /// </summary>
        /// <param name="admin">管理员信息</param>
        /// <param name="contrabandCategoryId">违禁品分类Id</param>
        /// <param name="requestDto">违禁品分类修改信息</param>
        /// <returns></returns>
        public ContrabandCategoryDto Update(ContrabandCategoryRequestDto requestDto, int contrabandCategoryId, AdminDto admin)
        {
            if (admin.CompanyId != 1)
            {
                throw new ArgumentException("您不是总公司员工，暂无权限修改");
            }
            if (requestDto.ContrabandCategory.Trim().Length > 30)
            {
                throw new ArgumentException("违禁品分类不能多于30字");
            }
            var categoryList = this.contrabandCategoryData.GetList(null).Result;
            if (!categoryList.Any(p => p.ContrabandCategoryId == contrabandCategoryId))
            {
                throw new ArgumentException("此违禁品分类信息不存在");
            }
            if (categoryList.Any(p => p.ContrabandCategoryId != contrabandCategoryId && p.ContrabandCategory == requestDto.ContrabandCategory.Trim()))
            {
                throw new ArgumentException("此违禁品分类已存在，请更换其他分类名称");
            }
            var result = categoryList.FirstOrDefault(p => p.ContrabandCategoryId == contrabandCategoryId);
            result.ContrabandCategory = requestDto.ContrabandCategory.Trim();
            result.UpdateTime = DateTime.Now;
            result.EditAdminId = admin.AdminId;
            result.EditAdminName = admin.FullName;
            this.contrabandCategoryData.UpdateAsync(result).GetAwaiter().GetResult();
            this.redisService.DeleteMultipleKey(key, false);
            return result.As<ContrabandCategoryDto>();
        }
        #endregion

        #region Delete
        /// <summary>
        /// 删除违禁品分类记录
        /// </summary>
        /// <param name="admin">管理员信息</param>
        /// <param name="contrabandCategoryId">违禁品分类Id</param>
        /// <returns></returns>
        public void Delete(AdminDto admin, int contrabandCategoryId)
        {
            if (admin.CompanyId != 1)
            {
                throw new ArgumentException("您不是总公司员工，暂无权限删除");
            }
            var result = this.contrabandCategoryData.GetEntityAsync(contrabandCategoryId).Result;
            if (result == null)
            {
                throw new ArgumentException("此违禁品分类信息不存在");
            }
            var contrabandConfigs = this.contrabandConfigData.GetByContrabandCategoryId(contrabandCategoryId).Result;
            if (contrabandConfigs.Any())
            {
                throw new ArgumentException("此违禁品分类已在违禁品配置使用，不允许删除");
            }
            this.contrabandCategoryData.DeleteAsync(contrabandCategoryId).GetAwaiter().GetResult();
            this.redisService.DeleteMultipleKey(key, false);
        }
        #endregion

        public PageableList<ContrabandCategoryDto> Query(AdminDto admin, string contrabandCategory, DateTime? createStartDate, DateTime? createEndDate, int pageIndex, int pageSize)
        {
            string cacheKey = this.redisService.GetKey(key, contrabandCategory, createStartDate, createEndDate, pageIndex, pageSize);
            var result = this.redisService.TryGet(cacheKey, () =>
            {
                var (data, dataCount) = this.contrabandCategoryData.Query(contrabandCategory, createStartDate, createEndDate, pageIndex, pageSize).Result;
                return new PageableList<ContrabandCategoryDto>()
                {
                    Count = dataCount,
                    Items = data.As<List<ContrabandCategoryDto>>(),
                    PageIndex = pageIndex,
                    PageSize = pageSize
                };
            }, TimeSpan.FromDays(30));
            return result;
        }

        public IEnumerable<ContrabandCategoryDto> GetList(AdminDto admin, string contrabandCategory)
        {
            string cacheKey = this.redisService.GetKey(key, contrabandCategory);
            var result = this.redisService.TryGet(cacheKey, () =>
            {
                var data = this.contrabandCategoryData.GetList(contrabandCategory).Result;
                return data.As<IEnumerable<ContrabandCategoryDto>>();
            }, TimeSpan.FromDays(1));
            return result;
        }
    }
}
